package com.yeyks.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.yeyks.base.Arguments;
import com.yeyks.base.PageInfo;
import com.yeyks.constant.ConfigKey;
import com.yeyks.dal.dao.AccountInfoMapper;
import com.yeyks.dal.dao.CompanyInfoMapper;
import com.yeyks.dal.dao.HotelInfoMapper;
import com.yeyks.dal.dao.RoomInfoMapper;
import com.yeyks.dal.domain.AccountInfo;
import com.yeyks.dal.domain.CompanyInfo;
import com.yeyks.dal.domain.HotelInfo;
import com.yeyks.dal.domain.RoomInfo;
import com.yeyks.dto.*;
import com.yeyks.exception.ServiceException;
import com.yeyks.model.em.AccountType;
import com.yeyks.model.em.HotelStatus;
import com.yeyks.model.enums.ComfortEnum;
import com.yeyks.model.enums.StarLevelEnum;
import com.yeyks.service.ConfigService;
import com.yeyks.service.HotelService;
import com.yeyks.util.*;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.yeyks.base.Arguments;
import com.yeyks.base.PageInfo;
import com.yeyks.dto.HotelCreateParam;
import com.yeyks.exception.ServiceException;
import com.yeyks.model.em.AccountType;
import com.yeyks.model.em.HotelStatus;
import com.yeyks.service.HotelService;
import com.yeyks.util.DateUtils;
import com.yeyks.util.ObjectConvertUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;


/**
 * @Author fuchangshuai
 * @date 2019/2/23 11:45 AM
 */
@Transactional
@Slf4j
@Service
public class HotelServiceImpl implements HotelService {
    @Autowired
    private HotelInfoMapper hotelInfoMapper;
    @Autowired
    private CompanyInfoMapper companyInfoMapper;
    @Autowired
    private AccountInfoMapper accountInfoMapper;
    @Autowired
    private RoomInfoMapper roomInfoMapper;
    @Autowired
    private ConfigService configService;
    @Autowired
    private HotelService hotelService;

    /**
     * 新增酒店(同时需要先增加公司信息，再增加用户，后增加酒店)
     *
     * @param createParam
     * @param id
     * @return
     */
    @Override
    public void createHotel(HotelCreateParam createParam, Integer id) {
        //首先创建公司，返回创建公司的id
        CompanyInfo companyInfo = changeCompany(createParam);
//        List<CompanyInfo> companyInfos = companyInfoMapper.selectByBizNameOrBizId(companyInfo.getBizName(), companyInfo.getBizNo());
//        if (companyInfos != null && companyInfos.size() != 0) {
//            throw new ServiceException("该酒店所属公司已经存在");
//        }
        Integer c = companyInfoMapper.insertReturnId(companyInfo);
        if (c != 1) {
            throw new ServiceException("创建公司失败");
        }

        //接着创建用户，返回创建用户的id
        AccountInfo accountInfo = changeAccount(createParam);
        accountInfo.setParentId(id);
        List<AccountInfo> existAccount = accountInfoMapper.selectByPhoneOrUsername(null, accountInfo.getUsername());
        if (existAccount != null && existAccount.size() != 0) {
            if (existAccount.get(0).getValid() != null && existAccount.get(0).getValid().equals(true)) {
                throw new ServiceException("该用户名已经存在");
            }
        }
        Integer a = accountInfoMapper.insertReturnId(accountInfo);
        if (a != 1) {
            throw new ServiceException("创建酒店账号失败");
        }
        //接着创建酒店
        HotelInfo hotelInfo = changeHotel(createParam);
        hotelInfo.setAdminId(id);
        hotelInfo.setCompanyId(companyInfo.getId());
        hotelInfo.setOperatorId(accountInfo.getId());
        hotelInfo.setPrincipalInfo(createParam.getPrincipal());
        hotelInfo.setStatus(HotelStatus.PreSubmit);
        hotelInfo.setIsDel(1);
        Integer h = hotelInfoMapper.insertReturnId(hotelInfo);
        if (h != 1) {
            throw new ServiceException("创建酒店失败");
        }
    }

    /**
     * 用户搜索酒店（2民宿，3三星级，4四星级，5五星级，6商务）
     *
     * @param city  城市名称，例：北京
     * @param checkIn    check-in日期，字符串描述，没有时间部分，例：2018-08-13
     * @param checkOut   check-out日期，字符串描述，没有时间部分，例：2018-08-16
     * @param price      价格（单位：分），默认值（0不限价），例：20000 （200元）
     * @param starLevel  星级：默认全部0，2民宿，3星级，6商务
     * @param keyword    关键字，通过酒店的名称
     * @param order      推荐(排序)模式：order 0智能排序（默认是这个），1距离（按照距离升序），2价格（按照价格升序），3价格（按照价格降序）
     * @param pageNum    当前页
     * @param pageSize   页码
     * @param positionX  经度
     * @param positionY  纬度
     * @return
     */
    @Override
    public Map<String,Object> searchHotel(String city, Long checkIn, Long checkOut, Integer price, Integer starLevel, String keyword, Integer order, Integer pageNum, Integer pageSize, Double positionX, Double positionY) {

        Map<String, Object> map = new HashMap<>();
        try {
            PageInfo pageInfo = PageInfo.of(pageNum, pageSize);
            String in = null;
            String out = null;
            if (checkIn != null && checkIn != 0) {
                in = DateUtils.stampToYYYYMMDD(checkIn);
            }
            if (checkOut != null && checkOut != 0) {
                out = DateUtils.stampToYYYYMMDD(checkOut);
            }

            map.put("city", city);
            map.put("checkIn", in);
            map.put("checkOut", out);
            map.put("price", price);
            if (starLevel == 0) {
                map.put("starLevel", null);
            } else {
                map.put("starLevel", starLevel);
            }
            if (Arguments.notEmpty(keyword)) {
                keyword = keyword.replaceAll("\\s", "");
            }
            map.put("keyword", keyword);
            map.put("order", order);
            map.put("offset", pageInfo.getOffset());
            map.put("limit", pageInfo.getLimit());
            map.put("positionX", positionX);
            map.put("positionY", positionY);
            List<Map> lists = hotelInfoMapper.searchHotel(map);
            Integer count = hotelInfoMapper.searchHotelCount(map);
            List<UserSearchHotelDTO> userSearchHotelDTOS = new ArrayList<>();
            if (lists == null || lists.size() == 0 || count == 0) {
                map.clear();
                map.put("list", userSearchHotelDTOS);
                map.put("count", count);
                return map;
            }
            //获取一个hotelInfo集合
            Map<Integer, HotelInfo> hotelInfoMap = getHotelInfo(lists);
            Map<Integer, AccountInfo> accountInfoMap = getAccountInfo(hotelInfoMap);
            //通过查询到的酒店的id，获取对应符合条件的房间集合
            Map<Integer, List<RoomInfo>> roomInfosMap = getRoomInfosV2(keyword, price, null, order, lists);
            for (Map list : lists) {
                Integer hotelId = ((Long) list.get("hotel_id")).intValue();

                UserSearchHotelDTO userSearchHotelDTO = new UserSearchHotelDTO();
                userSearchHotelDTO.setRoomInfos(roomInfosMap.get(hotelId));
                HotelInfo hotelInfo = hotelInfoMap.get(hotelId);
                HotelSearchDTO hotelSearchDTO = ObjectConvertUtil.convertObject(hotelInfo, HotelSearchDTO.class);
                AccountInfo exist = accountInfoMap.get(hotelInfo.getOperatorId());
                String tel = exist == null ? null : exist.getTel();
                if (!Arguments.notEmpty(tel)) {
                    tel = exist == null ? null : exist.getPhone();
                }
                if (!Arguments.notEmpty(tel)) {
                    tel = getPhoneByHotelInfo(hotelInfo);
                }
                hotelSearchDTO.setTel(tel);
                userSearchHotelDTO.setHotelInfo(hotelSearchDTO);
                changeStarToStr(userSearchHotelDTO, hotelInfo.getStarLevel());
                Double distance = Double.parseDouble(list.get("distance").toString());
                userSearchHotelDTO.setDistance(distance.intValue());
                userSearchHotelDTOS.add(userSearchHotelDTO);

            }
            map.clear();
            map.put("list", userSearchHotelDTOS);
            map.put("count", count);

        } catch (Exception e) {
            log.error("查询酒店出错{}", e.getLocalizedMessage());
            map.put("list", null);
            map.put("count", 0);
        }
        return map;

    }

    private Map<Integer,List<RoomInfo>> getRoomInfosNew(Integer price, Integer minPrice, List<Map> lists) {
        Map<Integer,List<RoomInfo>> resMap = new HashMap<>();
        Map<String, Object> map = new HashMap<>();
        map.put("price", price);
        map.put("minPrice", minPrice);
        for (Map list : lists) {
            Integer hotelId = ((Long) list.get("hotel_id")).intValue();
            map.put("hotelId", hotelId);
            List<RoomInfo> roomInfos = roomInfoMapper.selectRoomsByHotelIdNew(map);
            resMap.put(hotelId, roomInfos);
        }
        return resMap;
    }

    private Map<Integer,List<RoomInfo>> getRoomInfosV2(String keyword, Integer price, Integer minPrice, Integer order, List<Map> lists) {
        Map<Integer,List<RoomInfo>> resMap = new HashMap<>();
        Map<String, Object> map = new HashMap<>();
        map.put("keyword", keyword);
        map.put("price", price);
        map.put("minPrice", minPrice);
        for (Map list : lists) {
            Integer hotelId = ((Long) list.get("hotel_id")).intValue();
            map.put("hotelId", hotelId);
            List<RoomInfo> roomInfos = roomInfoMapper.selectRoomsByHotelId(map);
            //价格升序
            if (order == 2) {
                roomInfos.sort(Comparator.comparing(RoomInfo::getCurPrice));
            }
            //价格降序
            if (order == 3) {
                roomInfos.sort(Comparator.comparing(RoomInfo::getCurPrice).reversed());
            }
            resMap.put(hotelId, roomInfos);
        }
        return resMap;
    }


    /**
     * 通过酒店id搜索酒店
     *
     * @param hotelId
     * @return
     */
    @Override
    public HotelInfo selectHotelInfoById(Integer hotelId) {
        return hotelInfoMapper.selectByPrimaryKey(hotelId);
    }

    /**
     * 通过酒店id计算酒店的平均分
     *
     * @param hotelId
     * @return
     */
    @Override
    public Integer updateScore(Integer hotelId) {
        return hotelInfoMapper.updateScore(hotelId);
    }

    /**
     * 通过酒店的id查询酒店的详情
     *
     * @param hotelId
     * @return
     */
    @Override
    public HotelInfoDTO selectHotelRoomDetail(Integer hotelId) {
        HotelInfo hotelInfo = hotelInfoMapper.selectByPrimaryKey(hotelId);
        if (hotelInfo == null) {
            log.info("该酒店信息不存在{}", hotelId);
            throw new ServiceException("该酒店信息不存在");
        }
        if (hotelInfo.getComfortLevel() == null) {
            hotelInfo.setComfortLevel(1);
        }
        if (hotelInfo.getEnabledCoupon() == null) {
            hotelInfo.setEnabledCoupon(1);
        }
        HotelInfoDTO hotelInfoDTO = ObjectConvertUtil.convertObject(hotelInfo, HotelInfoDTO.class);
        AccountInfo accountInfo = accountInfoMapper.selectByPrimaryKey(hotelInfo.getOperatorId());
        if (accountInfo != null && Arguments.notEmpty(accountInfo.getTel())) {
            hotelInfoDTO.setPhone(accountInfo.getTel());
        } else {
            String principalInfo = hotelInfo.getPrincipalInfo();
            JSONObject jsonObject = JSONObject.parseObject(principalInfo);
            String phone = (String) jsonObject.get("phone");
            hotelInfoDTO.setPhone(phone);
        }
        changeStarToStr(hotelInfoDTO, hotelInfo.getStarLevel());

        hotelInfoDTO.setComfort(ComfortEnum.getDesc(hotelInfo.getComfortLevel()));
        setHotelPic(hotelInfoDTO, hotelInfo);
        //通过酒店id查询酒店的房间信息
        List<RoomInfo> roomInfos = roomInfoMapper.selectValidByHotelId(hotelId);
        List<RoomInfoDTO> roomInfoDTOS = getRoomInfoDTO(roomInfos, hotelInfoDTO.getEnabledCoupon());
        hotelInfoDTO.setRoomInfoDTOS(roomInfoDTOS);
        return hotelInfoDTO;
    }

    /**
     * 通过id进行删除（将isDel字段修改为0）
     *
     * @param id
     * @return
     */
    @Override
    public int deleteById(Integer id, Integer isDel) {
        return hotelInfoMapper.deleteById(id, isDel);
    }

    /**
     * 通过酒店信息获取酒店联系人的手机号（用于发短信）
     *
     * @param hotelInfo
     * @return
     */
    @Override
    public String getSmsPhoneByHotelInfo(HotelInfo hotelInfo) {
        String phone;
        //通过酒店所有人id查询酒店用户手机号
        AccountInfo accountInfo = accountInfoMapper.selectByPrimaryKey(hotelInfo.getOperatorId());
        phone = accountInfo == null ? null : accountInfo.getPhone();
        if (phone == null) {
            phone = getPhoneByHotelInfo(hotelInfo);
        }
        if (phone == null) {
            log.info("该酒店归属用户手机号不存在,hotelId = {}", hotelInfo.getId());
        }
        return phone;
    }

    /**
     * 通过酒店信息获取酒店固话，没有使用手机号
     *
     * @param hotelInfo
     * @return
     */
    @Override
    public String getTelByHotelInfo(HotelInfo hotelInfo) {
        String tel;
        //通过酒店所有人id查询酒店用户手机号
        AccountInfo accountInfo = accountInfoMapper.selectByPrimaryKey(hotelInfo.getOperatorId());
        tel = accountInfo == null ? null : accountInfo.getTel();
        if (tel == null) {
            tel = accountInfo == null ? null : accountInfo.getPhone();
        }
        if (tel == null) {
            tel = getPhoneByHotelInfo(hotelInfo);
        }
        if (tel == null) {
            log.info("该酒店固话不存在,hotelId = {}", hotelInfo.getId());
        }
        return tel;
    }

    /**
     * 用户搜索酒店新接口(通过星级)（2民宿，3三星级，4四星级，5五星级，6商务）
     *
     * @param city  城市名称，例：北京
     * @param checkIn    check-in日期，字符串描述，没有时间部分，例：2018-08-13
     * @param checkOut   check-out日期，字符串描述，没有时间部分，例：2018-08-16
     * @param price      价格（单位：分），默认值（0不限价），例：20000 （200元）
     * @param starLevel  星级：默认全部0，2民宿，3星级，6商务
     * @param positionX  经度
     * @param positionY  纬度
     * @return
     */
    @Override
    public Map<String, Object> searchHotelNew(String city, Long checkIn, Long checkOut, Integer price, Integer starLevel, Double positionX, Double positionY) {
        List<UserSearchHotelDTO> userSearchHotelDTOS = new ArrayList<>();
        String in = null;
        String out = null;
        if (checkIn != null && checkIn != 0) {
            in = DateUtils.stampToYYYYMMDD(checkIn);
        }
        if (checkOut != null && checkOut != 0) {
            out = DateUtils.stampToYYYYMMDD(checkOut);
        }
        Map<String, Object> map = new HashMap<>();
        map.put("city", city);
        map.put("checkIn", in);
        map.put("checkOut", out);
        map.put("price", price);
        if (starLevel == 0) {
            map.put("starLevel", null);
        } else {
            map.put("starLevel", starLevel);
        }
        map.put("positionX", positionX);
        map.put("positionY", positionY);
        Integer maxDistance;//距离范围
        Integer range;//price的75%
        Integer minCount = null;//搜索酒店最小数
        Integer maxCount = null;//搜索酒店最大数
        Integer limit;//搜索酒店范围
        String title = null;//搜索标题
        String noMessage = null;//没有酒店文案
        String message = null;//有酒店但没该价格区间的酒店
        try {
            String value = configService.getValue(ConfigKey.SEARCH_CONDITION);
            JSONObject jsonObject = JSONObject.parseObject(value);
            maxDistance = (Integer) jsonObject.get("distance");
            range = (Integer) jsonObject.get("range");
            minCount = (Integer) jsonObject.get("minCount");
            maxCount = (Integer) jsonObject.get("maxCount");
            limit = (Integer) jsonObject.get("limit");
            title = (String) jsonObject.get("title");
            noMessage = (String) jsonObject.get("noMessage");
            message = (String) jsonObject.get("message");
        } catch (Exception e) {
            maxDistance = 20000;
            range = 75;
            minCount = 5;
            maxCount = 15;
            limit = 100;
            title = "搜索结果";
            noMessage = "该地区酒店较少";
            message = "该地区酒店较少，请调整价格重新抢单";
        }
        Integer minPrice = FormatUtils.amountToRate(price, range);
        map.put("distance", maxDistance);
        map.put("minPrice", minPrice);
        map.put("limit", limit);
        List<Map> lists = hotelInfoMapper.searchHotelNew(map);
        if (lists == null || lists.size() == 0) {
            map.remove("price");
            List<Map> existLists = hotelInfoMapper.searchHotelNoPrice(map);
            map.clear();
            map.put("title", title);
            map.put("list", userSearchHotelDTOS);
            if (existLists == null || existLists.size() == 0) {
                map.put("message", noMessage);
            } else {
                map.put("message", message);
            }
            return map;
        }
        //获取一个hotelInfo集合
        Map<Integer, HotelInfo> hotelInfoMap = getHotelInfo(lists);
        Map<Integer, AccountInfo> accountInfoMap = getAccountInfo(hotelInfoMap);
        //通过查询到的酒店的id，获取对应符合条件的房间集合
        Map<Integer, List<RoomInfo>> roomInfosMap = getRoomInfosNew(price, minPrice, lists);
        for (Map list : lists) {
            Integer hotelId = ((Long) list.get("hotel_id")).intValue();
            UserSearchHotelDTO userSearchHotelDTO = new UserSearchHotelDTO();
            userSearchHotelDTO.setRoomInfos(roomInfosMap.get(hotelId));
            HotelInfo hotelInfo = hotelInfoMap.get(hotelId);
            if (hotelInfo.getEnabledCoupon() == null) {
                hotelInfo.setEnabledCoupon(1);
            }
            HotelSearchDTO hotelSearchDTO = ObjectConvertUtil.convertObject(hotelInfo, HotelSearchDTO.class);
            AccountInfo exist = accountInfoMap.get(hotelInfo.getOperatorId());
            String tel = exist == null ? null : exist.getTel();
            if (!Arguments.notEmpty(tel)) {
                tel = exist == null ? null : exist.getPhone();
            }
            if (!Arguments.notEmpty(tel)) {
                tel = getPhoneByHotelInfo(hotelInfo);
            }
            hotelSearchDTO.setTel(tel);
            userSearchHotelDTO.setHotelInfo(hotelSearchDTO);
            changeStarToStr(userSearchHotelDTO, hotelInfo.getStarLevel());
            try {
                Double distance = Double.parseDouble(list.get("distance").toString());
                userSearchHotelDTO.setDistance(distance.intValue());
            } catch (Exception e) {
                userSearchHotelDTO.setDistance(0);
            }
            userSearchHotelDTOS.add(userSearchHotelDTO);

        }
        map.clear();
        map.put("title", title);
        int index = 0;
        try {
            index = Utility.getRandom(minCount, maxCount);
        } catch (Exception e) {
            map.put("list", userSearchHotelDTOS);
            return map;
        }
        if (userSearchHotelDTOS.size() > index) {
            Collections.shuffle(userSearchHotelDTOS);
            map.put("list", userSearchHotelDTOS.subList(0, index));

        } else {
            map.put("list", userSearchHotelDTOS);
        }
        return map;

    }

    /**
     * 用户搜索酒店(通过舒适度)（默认1舒适 2高档 3豪华 4民宿专区）
     *
     * @param city  城市名称，例：北京
     * @param checkIn    check-in日期，字符串描述，没有时间部分，例：2018-08-13
     * @param checkOut   check-out日期，字符串描述，没有时间部分，例：2018-08-16
     * @param price      价格（单位：分），默认值（0不限价），例：20000 （200元）
     * @param starLevel  星级：默认1舒适 2高档 3豪华 4民宿专区
     * @param positionX  经度
     * @param positionY  纬度
     * @return
     */
    @Override
    public Map<String, Object> searchHotelV2(String city, Long checkIn, Long checkOut, Integer price, Integer starLevel, Double positionX, Double positionY) {
        List<UserSearchHotelDTO> userSearchHotelDTOS = new ArrayList<>();
        String in = null;
        String out = null;
        if (checkIn != null && checkIn != 0) {
            in = DateUtils.stampToYYYYMMDD(checkIn);
        }
        if (checkOut != null && checkOut != 0) {
            out = DateUtils.stampToYYYYMMDD(checkOut);
        }
        Map<String, Object> map = new HashMap<>();
        map.put("city", city);
        map.put("checkIn", in);
        map.put("checkOut", out);
        map.put("price", price);
        if (starLevel == 0) {
            map.put("starLevel", null);
        } else {
            map.put("starLevel", starLevel);
        }
        map.put("positionX", positionX);
        map.put("positionY", positionY);
        Integer maxDistance;//距离范围
        Integer range;//price的75%
        Integer minCount = null;//搜索酒店最小数
        Integer maxCount = null;//搜索酒店最大数
        Integer limit;//搜索酒店范围
        String title = null;//搜索标题
        String noMessage = null;//没有酒店文案
        String message = null;//有酒店但没该价格区间的酒店
        try {
            String value = configService.getValue(ConfigKey.SEARCH_CONDITION);
            JSONObject jsonObject = JSONObject.parseObject(value);
            maxDistance = (Integer) jsonObject.get("distance");
            range = (Integer) jsonObject.get("range");
            minCount = (Integer) jsonObject.get("minCount");
            maxCount = (Integer) jsonObject.get("maxCount");
            limit = (Integer) jsonObject.get("limit");
            title = (String) jsonObject.get("title");
            noMessage = (String) jsonObject.get("noMessage");
            message = (String) jsonObject.get("message");
        } catch (Exception e) {
            maxDistance = 20000;
            range = 75;
            minCount = 5;
            maxCount = 15;
            limit = 100;
            title = "搜索结果";
            noMessage = "该地区酒店较少";
            message = "该地区酒店较少，请调整价格重新抢单";
        }
        Integer minPrice = FormatUtils.amountToRate(price, range);
        map.put("distance", maxDistance);
        map.put("minPrice", minPrice);
        map.put("limit", limit);
        List<Map> lists = hotelInfoMapper.searchHotelV2(map);
        if (lists == null || lists.size() == 0) {
            map.remove("price");
            List<Map> existLists = hotelInfoMapper.searchHotelNoPriceV2(map);
            map.clear();
            map.put("title", title);
            map.put("list", userSearchHotelDTOS);
            if (existLists == null || existLists.size() == 0) {
                map.put("message", noMessage);
            } else {
                map.put("message", message);
            }
            return map;
        }
        //获取一个hotelInfo集合
        Map<Integer, HotelInfo> hotelInfoMap = getHotelInfo(lists);
        Map<Integer, AccountInfo> accountInfoMap = getAccountInfo(hotelInfoMap);
        //通过查询到的酒店的id，获取对应符合条件的房间集合
        Map<Integer, List<RoomInfo>> roomInfosMap = getRoomInfosNew(price, minPrice, lists);
        for (Map list : lists) {
            Integer hotelId = ((Long) list.get("hotel_id")).intValue();
            UserSearchHotelDTO userSearchHotelDTO = new UserSearchHotelDTO();
            userSearchHotelDTO.setRoomInfos(roomInfosMap.get(hotelId));
            HotelInfo hotelInfo = hotelInfoMap.get(hotelId);
            HotelSearchDTO hotelSearchDTO = ObjectConvertUtil.convertObject(hotelInfo, HotelSearchDTO.class);
            AccountInfo exist = accountInfoMap.get(hotelInfo.getOperatorId());
            String tel = exist == null ? null : exist.getTel();
            if (!Arguments.notEmpty(tel)) {
                tel = exist == null ? null : exist.getPhone();
            }
            if (!Arguments.notEmpty(tel)) {
                tel = getPhoneByHotelInfo(hotelInfo);
            }
            hotelSearchDTO.setTel(tel);
            userSearchHotelDTO.setHotelInfo(hotelSearchDTO);
            userSearchHotelDTO.setStar(ComfortEnum.getDesc(hotelInfo.getComfortLevel()));
//            changeStarToStr(userSearchHotelDTO, hotelInfo.getStarLevel());
            try {
                Double distance = Double.parseDouble(list.get("distance").toString());
                userSearchHotelDTO.setDistance(distance.intValue());
            } catch (Exception e) {
                userSearchHotelDTO.setDistance(0);
            }
            userSearchHotelDTOS.add(userSearchHotelDTO);

        }
        map.clear();
        map.put("title", title);
        int index = 0;
        try {
            index = Utility.getRandom(minCount, maxCount);
        } catch (Exception e) {
            map.put("list", userSearchHotelDTOS);
            return map;
        }
        if (userSearchHotelDTOS.size() > index) {
            Collections.shuffle(userSearchHotelDTOS);
            map.put("list", userSearchHotelDTOS.subList(0, index));

        } else {
            map.put("list", userSearchHotelDTOS);
        }
        return map;

    }

    private String getPhoneByHotelInfo(HotelInfo hotelInfo) {
        String phone;
        try {
            JSONObject jsonObject = JSONObject.parseObject(hotelInfo.getPrincipalInfo());
            phone = (String) jsonObject.get("phone");
            return phone;
        } catch (Exception e) {
            return null;
        }
    }

    private void setHotelPic(HotelInfoDTO hotelInfoDTO, HotelInfo hotelInfo) {
        String extraInfo = hotelInfo.getExtraInfo();
        JSONObject jsonObject = JSONObject.parseObject(extraInfo);
        List<String> imgUrlList = (List<String>) jsonObject.get("imgUrlList");
        hotelInfoDTO.setHotelPics(imgUrlList);
    }

    private List<RoomInfoDTO> getRoomInfoDTO(List<RoomInfo> roomInfos, Integer isUse) {
        List<RoomInfoDTO> roomInfoDTOS = new ArrayList<>();
        for (RoomInfo roomInfo : roomInfos) {
            RoomInfoDTO roomInfoDTO = ObjectConvertUtil.convertObject(roomInfo, RoomInfoDTO.class);
            roomInfoDTO.setEnabledCoupon(isUse);
            String extraInfo = roomInfo.getExtraInfo();
            JSONObject jsonObject = JSONObject.parseObject(extraInfo);
            List<String> imgUrlList = (List<String>) jsonObject.get("imgUrlList");
            roomInfoDTO.setPicUrls(imgUrlList);
            roomInfoDTOS.add(roomInfoDTO);
        }
        return roomInfoDTOS;
    }

    private void changeStarToStr(HotelInfoDTO hotelInfoDTO, Integer starLevel) {

        if (starLevel.equals(StarLevelEnum.HOMESTAY.value())) {
            hotelInfoDTO.setStar(StarLevelEnum.HOMESTAY.desc());
        }
        if (starLevel.equals(StarLevelEnum.THREESTAR.value())) {
            hotelInfoDTO.setStar(StarLevelEnum.THREESTAR.desc());
        }
        if (starLevel.equals(StarLevelEnum.FOURSTAR.value())) {
            hotelInfoDTO.setStar(StarLevelEnum.FOURSTAR.desc());
        }
        if (starLevel.equals(StarLevelEnum.FIVESTAR.value())) {
            hotelInfoDTO.setStar(StarLevelEnum.FIVESTAR.desc());
        }
        if (starLevel.equals(StarLevelEnum.BUSINESS.value())) {
            hotelInfoDTO.setStar(StarLevelEnum.BUSINESS.desc());
        }
    }

    private void changeStarToStr(UserSearchHotelDTO userSearchHotelDTO, Integer starLevel) {

        if (starLevel.equals(StarLevelEnum.HOMESTAY.value())) {
            userSearchHotelDTO.setStar(StarLevelEnum.HOMESTAY.desc());
        }
        if (starLevel.equals(StarLevelEnum.THREESTAR.value())) {
            userSearchHotelDTO.setStar(StarLevelEnum.THREESTAR.desc());
        }
        if (starLevel.equals(StarLevelEnum.FOURSTAR.value())) {
            userSearchHotelDTO.setStar(StarLevelEnum.FOURSTAR.desc());
        }
        if (starLevel.equals(StarLevelEnum.FIVESTAR.value())) {
            userSearchHotelDTO.setStar(StarLevelEnum.FIVESTAR.desc());
        }
        if (starLevel.equals(StarLevelEnum.BUSINESS.value())) {
            userSearchHotelDTO.setStar(StarLevelEnum.BUSINESS.desc());
        }
    }

    private Map<Integer, HotelInfo> getHotelInfo(List<Map> lists) {
        LinkedHashSet<Integer> set = new LinkedHashSet<>();
        for (Map list : lists) {
            set.add(((Long) list.get("hotel_id")).intValue());
        }
        List<HotelInfo> hotelInfos = hotelInfoMapper.selectByIds(new ArrayList<>(set));
        return Maps.uniqueIndex(hotelInfos, HotelInfo::getId);
    }

    private Map<Integer, AccountInfo> getAccountInfo(Map<Integer, HotelInfo> hotelInfoMap) {
        List<HotelInfo> hotelInfos = new ArrayList<>();
        for (Map.Entry<Integer, HotelInfo> entry : hotelInfoMap.entrySet()) {
            hotelInfos.add(entry.getValue());
        }
        List<Integer> operatorIds = Lists.transform(hotelInfos, HotelInfo::getOperatorId);
        List<AccountInfo> accountInfos = accountInfoMapper.selectByOperatorIds(operatorIds);
        Maps.uniqueIndex(accountInfos, AccountInfo::getId);
        return Maps.uniqueIndex(accountInfos, AccountInfo::getId);
    }

    private HotelInfo changeHotel(HotelCreateParam createParam) {

        return ObjectConvertUtil.convertObject(createParam, HotelInfo.class);
    }

    private AccountInfo changeAccount(HotelCreateParam createParam) {

        AccountInfo accountInfo = ObjectConvertUtil.convertObject(createParam, AccountInfo.class);
        accountInfo.setValid(createParam.getAccountValid());
        accountInfo.setType(AccountType.HotelManager);
        accountInfo.setExtraInfo(createParam.getAccountExtraInfo());
        return accountInfo;
    }

    private CompanyInfo changeCompany(HotelCreateParam createParam) {
        CompanyInfo companyInfo = ObjectConvertUtil.convertObject(createParam, CompanyInfo.class);
        companyInfo.setExtraInfo(createParam.getHotelExtraInfo());
        companyInfo.setAddress(createParam.getHotelAddress());
        companyInfo.setPrincipalInfo(createParam.getHotelPrincipalInfo());
        return companyInfo;
    }
}
